package com.xp.ai.tools;

import com.xp.ai.util.ModelUtils;
import dev.langchain4j.agent.tool.Tool;
import dev.langchain4j.agent.tool.ToolExecutionRequest;
import dev.langchain4j.agent.tool.ToolSpecification;
import dev.langchain4j.agent.tool.ToolSpecifications;
import dev.langchain4j.data.message.AiMessage;
import dev.langchain4j.data.message.ChatMessage;
import dev.langchain4j.data.message.ToolExecutionResultMessage;
import dev.langchain4j.data.message.UserMessage;
import dev.langchain4j.memory.chat.MessageWindowChatMemory;
import dev.langchain4j.model.chat.ChatLanguageModel;
import dev.langchain4j.model.chat.request.ChatRequest;
import dev.langchain4j.model.chat.request.ChatRequestParameters;
import dev.langchain4j.model.chat.response.ChatResponse;
import dev.langchain4j.model.moderation.ModerationModel;
import dev.langchain4j.model.openai.OpenAiChatModel;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

/**
 *
 *
 *  本地方法增强大模型
 */
public class WithToolsChat {

    /***
     * 定制本地话的方法，形成大模型的Tools 增强工具
     *
     */
    @Tool("当前日期")
    //因为要在 static 中调用 ，所以这里得是 static 得 不然找不到会报错得
    public static String now(){
        System.out.println("now 调用");
        return LocalDateTime.now().toString();
    }

    @Tool("Get weather of an location, the user shoud supply a location first")
    public String  get(){
        return "晴天";
    }
    public static void main(String[] args) throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {

        ChatLanguageModel chatModel = ModelUtils.getDeepSeeV3Model();
//        ChatLanguageModel chatModel = ModelUtils.getAliZpModel();

        //基础测试方法
        UserMessage userMessage = UserMessage.from("今天是几月几号？");
//        ChatResponse response = chatModel.chat(userMessage);
//        AiMessage aiMessage = response.aiMessage();
//        System.out.println(aiMessage.text());

        //这里是获取本地增强方法
        ToolSpecification toolSpecification = ToolSpecifications.toolSpecificationFrom(WithToolsChat.class.getMethod("now"));

        ChatRequestParameters chatRequestParameters = ChatRequestParameters.builder()
                .toolSpecifications(toolSpecification)
                .build();
        ChatRequest chatRequest = ChatRequest.builder()
                .messages(userMessage)
                .parameters(chatRequestParameters)
                .build();
        ChatResponse toolResponse = chatModel.chat(chatRequest);
        AiMessage aiMessage1 = toolResponse.aiMessage();
        System.out.println(aiMessage1);
        if (aiMessage1.hasToolExecutionRequests()) {
            List<ToolExecutionRequest> toolExecutionRequests = aiMessage1.toolExecutionRequests();
            for (ToolExecutionRequest toolExecutionRequest : toolExecutionRequests) {
                String name = toolExecutionRequest.name();
                //因为我们知道这里是这个方法，所以直接调用即可
                Method method = WithToolsChat.class.getMethod(name);
                String res = (String) method.invoke(null);
                System.out.println(res);
                //将执行的结果封装为工具消息
                ToolExecutionResultMessage toolExecutionResultMessage = ToolExecutionResultMessage.from(toolExecutionRequest.id(), toolExecutionRequest.name(), res);
//                List<ChatMessage> list = new ArrayList<>();
//                list.add(userMessage);
//                list.add(aiMessage1);
//                list.add(toolExecutionResultMessage);
//                ChatResponse chatResponse = chatModel.chat(list);
                ChatResponse chatResponse = chatModel.chat(userMessage, aiMessage1, toolExecutionResultMessage);
                AiMessage aiMessage2 = chatResponse.aiMessage();
                String text = aiMessage2.text();
                System.out.println(text);
            }
        }

    }
}
